事件其实就是阻塞所有线程,让所有的线程进入等待的状态

from threading import Event

e = Event()
e.wait(5)  # 得到一个标识,表示的默认状态就是阻塞,如果传了一个数字进去就代表只阻塞5秒,如果不传一直阻塞着
e.set()  # 将标识变成非阻塞状态
e.clear()  # 将标识变成阻塞状态
e.is_set()  # 判断是否为非阻塞 返回值: True: 非阻塞 False: 阻塞

1. 红绿灯例子

  • 每隔3秒进行红绿灯的切换
  • 每次绿灯都会通过一定随机数量的车辆

import random
import time
from threading import Thread
from threading import Event


# 红绿灯切换线程
def traffic_light(e):
    while True:
        if e.is_set():  # 判断是否为非阻塞
            time.sleep(3)
            print('红灯亮')
            e.clear()  # 将标识设置为阻塞
        else:
            time.sleep(3)
            print('绿灯亮')
            e.set()  # 将标识设置为非阻塞


# 汽车通过线程
def car(i, e):
    e.wait()  # 设置标识状态,根据状态对所有线程进行阻塞
    print('%s车通过' % i)


e = Event()  # 立了一个红绿灯
tra = Thread(target=traffic_light, args=(e,))
tra.start()  # 执行红绿灯切换线程

for i in range(100):
    if i % 6 == 0:
        time.sleep(random.randint(1, 3))  # 设置延时,每次通过随机数量的车辆
    car_pro = Thread(target=car, args=(i, e))
    car_pro.start()  # 汽车通过线程

2. 连接数据库例子

  • 连接3次数据库
  • 每0.5秒连接一次
  • 如果连接成功,就显示成功,否者就报错

import time
import random
from threading import Thread
from threading import Event


def conn_mysql():
    count = 1
    while not e.is_set():  # 判断标识状态是否为阻塞
        if count > 3:  # 如果超过三次就抛出异常
            raise TimeoutError  # 手动抛出异常
        print('尝试连接第%s次' % count)
        count += 1
        e.wait(0.5)  # 只阻塞 0.5 秒
    print('连接成功')


def check_conn():
 # 检测数据库服务器的连接是否正常
    time.sleep(random.randint(1, 2))  # 模拟连接检测的时间
    e.set()  # 将标识状态设置为非阻塞


e = Event()
check = Thread(target=check_conn)
check.start()
conn = Thread(target=conn_mysql)
conn.start()